#pragma once
#include "Common.h"
#include "ThreadCache.h"
#include "PageCache.h"
#include "ObjectPool.h"

static void* ConcurrentAlloc(size_t size)
{
	if (size > MAX_BYTES)
	{
		size_t aliginSize = SizeClass::RoudUp(size);
		size_t kpage = aliginSize >> PAGE_SHIFT;
		PageCache::GetInstance()->_pagemtx.lock();
		Span* span = PageCache::GetInstance()->NewSpan(kpage);
		span->objSize = size;
		PageCache::GetInstance()->_pagemtx.unlock();
		void* ptr = (void*)(span->_pageId << PAGE_SHIFT);
		return ptr;
	}

	if (pTLSThreadCache == nullptr)
	{
		static ObjectPool<ThreadCache> tcPool;
		//pTLSThreadCache = new ThreadCache;
		pTLSThreadCache = tcPool.New();
	}
	cout << std::this_thread::get_id() << " : " << pTLSThreadCache << endl;
	return pTLSThreadCache->Allocate(size);
}

static void ConcurrentFree(void* ptr)
{
	Span* span = PageCache::GetInstance()->MapObjectToSpan(ptr);
	size_t size = span->objSize;
	if (size > MAX_BYTES)
	{
		Span* span = PageCache::GetInstance()->MapObjectToSpan(ptr);
		PageCache::GetInstance()->_pagemtx.lock();
		PageCache::GetInstance()->ReleaseSpanToPageCache(span);
		PageCache::GetInstance()->_pagemtx.unlock();
	}
	assert(pTLSThreadCache);
	pTLSThreadCache->DeAllocate(ptr, size); //TODO
}